package model.search;

import java.util.HashMap;
import java.util.List;
import java.util.Vector;

import model.basics.ClassRoom;
import model.basics.Request;
import model.basics.Resource;
import model.time.IllegalTimeValuesException;
import model.time.InvalidMinutesException;
import model.time.NullParametersReceivedExpeption;

/**
 * This class is in charge of the methods that search for the appropriate classroom. This depends of the information we pass them.
 * @author Alexis
 * 
 */
public class Validator {

	
	/**
	 * Search for classroom that satisfy whit all the information we pass it.
	 * 
	 * @param crs
	 * @param req1
	 * @param ress
	 * @param allOrd
	 * */
	public List<ClassRoom> calculateSatisfactionForAllItems(
			List<ClassRoom> crs, Request req1, List<Resource> ress,
			List<Order> allOrd) throws NullParametersReceivedExpeption,
			InvalidMinutesException, IllegalTimeValuesException {

		//returns all classroom that satisfy all items asked and accomplish whit the capacity specify
		
		HashMap<Resource, Integer> hmResReq = req1.getResources();

		int crCapacity = req1.getCapacity();
		List<ClassRoom> crsResult = new Vector<ClassRoom>();

		// iterator over classrooms
		for (int i = 0; i < crs.size(); i++) {
			// check for capacity
			if (crs.get(i).getMaxCapacity() >= crCapacity) {
				HashMap<Resource, Integer> hmResCr = crs.get(i).getResources();
				int count = 0;

				// iterator over all resources
				for (int k = 0; k < ress.size(); k++) {
					//if the resource k is in the request hashMap 
					if (hmResReq.containsKey(ress.get(k))) {
						// if the resource is in the list of resources of the classroom
						if (hmResCr.containsKey(ress.get(k))) {
							// if satisfy the quantity of resources
							if (hmResCr.get(ress.get(k)) >= hmResReq.get(ress
									.get(k)))

								count++;
						}
					}
				}
				if (count == hmResReq.size())
					crsResult.add(crs.get(i));

			}
		}
		crsResult = this.CalculateSatisfactionForTimeFrame(crsResult, req1,allOrd);
		return crsResult;

	}

	/**
	 * Search for classroom that satisfy whit the capacity of a classroom
	 * @param crs
	 * @param req1
	 * @param ress
	 * 
	 * */
	
	public List<ClassRoom> calculateSatisfactionForClassRoom(
			List<ClassRoom> crs, Request req1, List<Resource> ress) {
		//returns a list of classrooms that satisfy with the capacity only

		int crCapacity = req1.getCapacity();
		List<ClassRoom> crsResult = new Vector<ClassRoom>();

		// iterator over all resources
		for (int i = 0; i < crs.size(); i++) {
			// check capacity
			if (crs.get(i).getMaxCapacity() >= crCapacity)
				crsResult.add(crs.get(i));
		}
		return crsResult;
	}

	
	/**
	 * Search for classroom that satisfy whit the resources
	 * @param crs
	 * @param req1
	 * @param ress
	 * */
	public List<ClassRoom> calculateSatisfactionForResources(
			List<ClassRoom> crs, Request req1, List<Resource> ress) {

		//returns a list of classrooms that have all the items asked and satisfy with the capacity

		HashMap<Resource, Integer> hmResReq = req1.getResources();

		int crCapacity = req1.getCapacity();
		List<ClassRoom> crsResult = new Vector<ClassRoom>();

		// iterator over all resources
		for (int i = 0; i < crs.size(); i++) {
			// check capacity
			if (crs.get(i).getMaxCapacity() >= crCapacity) {
				HashMap<Resource, Integer> hmResCr = crs.get(i).getResources();
				int count = 0;

				// iterator over all resources
				for (int k = 0; k < ress.size(); k++) {
					//if the resource k is in the request hashMap 
					if (hmResReq.containsKey(ress.get(k))) {
						// if the resource is in the list of resources of the classroom
						if (hmResCr.containsKey(ress.get(k))) {
							// if satisfy the quantity of resources
							if (hmResCr.get(ress.get(k)) >= hmResReq.get(ress
									.get(k)))

								count++;
						}
					}
				}
				if (count == hmResReq.size())
					crsResult.add(crs.get(i));

			}
		}
		return crsResult;

	}

	/**
	 * Search for classroom that satisfy whit the time frames
	 * 
	 * @throws IllegalTimeValuesException
	 * @throws InvalidMinutesException
	 * @throws NullParametersReceivedExpeption
	 */
	
	
	public List<ClassRoom> CalculateSatisfactionForTimeFrame(
			List<ClassRoom> crs, Request req, List<Order> allOrd)
			throws NullParametersReceivedExpeption, InvalidMinutesException,
			IllegalTimeValuesException {

		List<ClassRoom> crsResult = new Vector<ClassRoom>();
		// iterate over classrooms
		for (int i = 0; i < crs.size(); i++) {
			boolean freeCR = true;
			if (!(crs.get(i).getOrders().isEmpty())) {

				// iterate over classroom's orders
				for (int j = 0; j < crs.get(i).getOrders().size(); j++) {
					// iterate over order's time frames
					for (int k = 0; k < crs.get(i).getOrders().get(j)
							.getTimeFrames().size(); k++) {
						// iterate over request's time frames
						for (int l = 0; l < req.getTimeFrames().size(); l++) {
							freeCR = freeCR
									&& (!(crs.get(i).getOrders().get(j)
											.getTimeFrames().get(k)
											.isOverlapped(req.getTimeFrames()
													.get(l))));

						}
					}

				}

			}
			if (freeCR)
				crsResult.add(crs.get(i));
		}

		return crsResult;
	}

}
